<?php
/**
 * BasicTable is a class to dumping of data from a database in an array.  This basic version makes an HTML output
 * @package CFtable
 * @author Chris Tyler
 * @version 1.0
 * @BasicTable is the base class for the an extensable HTML table class for array based data.  This provides data display, sorting, filtering, paging and heading functions
 * @copyright 2007-2008 
 */
class CF_TableSlick {
	/**
	* @var array $valuesarray A 2D array of values, an array of associative row arrays, valuesarray[<row number>][<column heading>]
	*/
	var $valuesarray;
	/**
	* @var array $currentrow holds the current associative array row being processed.  Use this to access other values in the same row in make functions.
	*/	

	/**
	*@var $prefetchparams - A string of parameters to prefix to remote request url
	*
	*/
	var $prefixparamstring = '?mode=jsonp';
	
	var $trigger_param = 'sel';

	var $fieldspec;
	/**
	* @var string $row_status Internal variable for determing odd or even row in table
	*/	

	var $name;	
	/**
	* @var bool $show_all_rows Set to true to show all rows regardless of fieldspec in basic table
	*/

	var $actionpage;

	/**
	 *  BasicTable Constructor method will form table from spec and values
	 * Default will show all columns
	 * all checked rows at once.
	 * @param array $the_spec  This is fieldspec array.  defaults to show all rows
	 * @param array $values array.  This is 2d array by rows
	 */
	function __construct( $the_spec = 'all', $values_array = '', $name = ''){
		$this->values_array = $values_array;
		$this->name = $name;
		if(is_array($the_spec)){
			$this->fieldspec = $the_spec;
			$this->show_all_rows = false;
			}
		else{
			$this->show_all_rows = true;
			}	
		$this->prefixparamstring = $this->prefixparamstring . '&sel=' . $this->name;
			
	}

	function CF_TableSlick( $the_spec = 'all', $values_array = ''){
		$this->__construct($the_spec, $values_array);
	}

	
	/**
	 *  set_valuesarray Method will set values arfixparamstringray to passed array
     * @param array $dataarray  This is array.  
	 */
	function set_valuesarray($dataarray){
		$this->valuesarray = $dataarray;	
	}	

	function set_name($name){
		$this->name = $name;
	}

	function set_actionpage($pagename){
		$this->actionpage = $pagename;
	}	
	
/**
 * Set FieldSpec Function
 * @param array $thespec - The fieldspec array
 * @param array $thespec [<colname>] - Set for each column, as named in the database query used
 * @param array $thespec [<colname>] ['headname'] (opt) - Name to display on the header for the column.  If not there, will use <colname>
 * @param array $thespec [<colname>] [key] - If set (1), this will be used as a key field for record operations
 * @param array $thespec [<colname>] [show] - If set (1), this column will show in displays.  If 0 or unset, column will not appear
 * @param array $thespec [<colname>] [select] - How to display editable boxes: {T = Text Input, C = Check box (0 or 1), D = drop down) 
 * @param array $thespec [<colname>] [list] = array of values (showvalue, keyvalue) to use in drop-down.  Array is of form:  valueslist [<index integer>][<keyvariablename>][<showvariablename>] Where defaults are keyvariablename = 'keyvalue' showvariable='showvalue' unless re-assigned
 * @param array $thespec [<colname>] [showvalue] - (opt)  Re-assignes the <keyvariablename> to the string specified, instead of 'keyvalue'
 * @param array $thespec [<colname>] [keyvalue] - (opt) Re-assignes the <showvariablename> to the string specified, instead of 'showvalue'
 * @param array $thespec [<colname>] [sort] - Specifies if row header will sort or not, {true, false, (or undefined)}
 * @param array $thespec [<colname>] [filter] - Specifies if row is filtered. if set= 'keyword', then will  bet textbox for LIKE '%keyword%' search.  If set (= 1, but not specific setting ), then will filter using spec from edit criteria ([select],[list],)
 */		
	function set_fieldspec($thespec){
		$this->fieldspec = $thespec;
	}

	function write_columns($col_array_name){
		$js_cols = "var $col_array_name = [\n";
		$divider = "";
		foreach($this->fieldspec AS $column=>$colspec){
			if(!empty($colspec['show'])){
				$js_cols .= $divider . $this->write_column($column,$colspec);
				$divider = ",\n";
			}
		}
		$js_cols .= "\n];\n";
		return $js_cols;
	}
	
	
	function write_column($column,$colspec){
		
		$js_col = '{';
		$js_col .= 'id:"' . $column . '" ';
		(isset($colspec['headname']))?$js_col .= ', name:"' . $colspec['headname'] . '" ':$js_col .= ', name:"' . $column . '" ';
		$js_col .= ', field:"' . $column . '" ';
		if(isset($colspec['size'])){$js_col .= ', width:"' . $colspec['size'] * 6 . '" ';}
		if($colspec['show'] == 'E'){
			if($colspec['select'] == 'T'){$js_col .= ', editor: TextCellEditor ';}
			if($colspec['select'] == 'A'){$js_col .= ', editor: LongTextCellEditor ';}
			if($colspec['select'] == 'CAL'){$js_col .= ', formatter: DateCellFormatter, 
editor: DateCalendarEditor , DateSourceFormat: "yy-mm-dd" , DateShowFormat: "mm/dd/yy" ';}	
			if($colspec['select'] == 'C'){$js_col .= ', formatter: BoolCellFormatterTF, editor: BoolCheckboxCellEditor , 
truefalse: {istrue: 1, isfalse: 0} 	';}		
			if($colspec['select'] == 'D'){$js_col .= ", editor: LookupListEditor , 
formatter: LookupListFormatter, lookupList: " . $this->name . "_lookup['$column'], lookupIndex: " . $this->name . "_lookup_idx['$column'] ";}			
		}
		$js_col .= '}';
		return $js_col;
	}

	function write_options($opt_array_name){
		$js_opt = "var $opt_array_name = {\n";
		
		$js_opt .= "		editable: true,\n";
		$js_opt .= "		enableAddRow: false,\n";
		$js_opt .= "		enableCellNavigation: true,\n";
		$js_opt .= "		asyncEditorLoading: false,\n";
		$js_opt .= "		editCommandHandler: " . $this->name . "_QandX\n";		
		
		$js_opt .= "};\n";
	
		return $js_opt;
	}
	
private function write_js_item_key_value(){
	$predelimiter = "";
	foreach($this->fieldspec AS $column=>$colspec){
		if(!empty($colspec['key'])){
			$js .= $predelimiter . "item['$column']";
			$predelimiter = " + ',' + ";
		}
	}
	return $js;
}

private function write_js_item_key_set(){
	$predelimiter = "";
	foreach($this->fieldspec AS $column=>$colspec){
		if(!empty($colspec['key'])){
			$js .= $predelimiter . $column;
			$predelimiter = " + ',' + ";
		}
	}
	return $js;
}
	
function write_js(){
$tbl_js = '';
$tbl_js .= 'var ' . $this->name . '_grid;
		var ' . $this->name . '_data = [];		
		var ' . $this->name . '_lookup = [];
		var ' . $this->name . '_lookup_idx = [];';


$tbl_js .= '
		$(function()
		{
		';
		
			
$tbl_js .= '
		var commandQueue = [];			
		$.ajaxSetup({cache: false});
';


	foreach($this->fieldspec AS $column=>$colspec){
		if($colspec['select'] == 'D'){
			$tbl_js .= '
 $.ajax({  
   url: "'. $this->actionpage . '?mode=jsonlookup&sel=' . $this->name . '&col=' . $column . '",  
   dataType: "json",  
   async: false,  
   success: function(data){  
   		var thisindex = [];
			' . $this->name . '_lookup["' . $column . '"] = data;
			for(x in ' . $this->name . '_lookup["' . $column . '"]){
				thisindex[' . $this->name . '_lookup["' . $column . '"][x].keyvalue] = ' . $this->name . '_lookup["' . $column . '"][x].showvalue;
			}
			' . $this->name . '_lookup_idx["' . $column . '"] = thisindex;
			}
		});	
';


		}
	}




$tbl_js .='
		
		function ' . $this->name . '_QandX(item,column,editCommand) {
		    commandQueue.push(editCommand);
		    $.get("' . $this->actionpage   . '",{sel: "' . $this->name . '", mode: "update", ks: "' . $this->write_js_item_key_set() . '", kv: ' . $this->write_js_item_key_value() . ', field: column.field, value: editCommand.serializedValue},   function(data){
     if(data.status == "OK"){
     		editCommand.execute();
     }else{
     		alert("Data Sync Error: " + data.msg);
     }
   },"json");

		}



		function ' . $this->name . '_undo() {
		    var command	 = commandQueue.pop();
		    if (command && Slick.GlobalEditorLock.cancelCurrentEdit()) {
		        command.undo();
		        grid.gotoCell(command.row,command.cell,false);
		    }
		}
		
			
';
	
$tbl_js .= $this->write_columns('columns');



$tbl_js .= $this->write_options('options');	
						
$tbl_js .= '		
	
			//retrieve comments to display on page
			$.getJSON("' . $this->actionpage . $this->prefixparamstring . '&jsoncallback=?", function(' . $this->name . '_data) { 
';


		
		
		
$tbl_js .= '
		
				' . $this->name . '_grid = new Slick.Grid($("#' . $this->name . '_grid"), ' . $this->name . '_data, columns, options);

				});


			
		});	
';
return $tbl_js;
}

	function write_html(){
		$html = "<div id='" . $this->name . "_grid" . "' style='width:100%;height:500px;'> </div>\n";
		return $html;
	
		
	}
	
	function maketable(){
		$out = $this->write_html();
		$out .= "<script>\n";
		$out .= $this->write_js();
		$out .= "</script>";
		echo $out;
	
	}
	
}


?>
